package com.bigflexlib.ds.op
{
	
	import com.bigflexlib.ds.container.IRContainer;
	

	public class ContainerBiggestOp extends AbstractContainerBestOp
	{

		
		private var iCompareFunction:Function;





		/**
		 * 
		 * 
		 * 
		 * 
		 * @param iContainer
		 * @param iCompareFunction
		 * @param iValueHandlerFunction
		 * @param emptyValue
		 * 
		 */
		public function ContainerBiggestOp( iContainer:IRContainer, iCompareFunction:Function, iValueHandlerFunction:Function, emptyValue:* )
		{
			
			this.iCompareFunction = iCompareFunction;
			
			super( iContainer, iValueHandlerFunction, emptyValue );
		}
		
		
		

		override protected function findBest( elements:IRContainer, bestSoFar:* = undefined ):*
		{
		
			return findBiggest( elements, compare, bestSoFar );
		
		}

		

		/**
		 * 
		 * This function seem redundant, but it helps us to create ContainerSmallestOp as a subclass
		 * 
		 * @param compareFunction
		 * @param e1
		 * @param e2
		 * @return 
		 * 
		 */		
		protected function compare(  e1:*, e2:* ):int
		{
			return iCompareFunction.apply( null, [ e1, e2 ] ) as int;
		}
		
		
		
		
		
		/**
		 * 
		 * this function is in the internal namespace so it can be unit tested
		 * it could be in an external utility class, but that would probably be over-architecture
		 * 
		 * @param elements
		 * @param biggestSoFar
		 * @return 
		 * 
		 */		
		internal static function findBiggest( elements:IRContainer, compareFunction:Function, biggestSoFar:* = undefined ):*
		{
			
			elements.walk( function( e:*, m:int ):void {

				if (  (biggestSoFar === undefined) || ( compareFunction.apply( null, [ biggestSoFar, e ] ) == -1 ) )
				{
					biggestSoFar = e;
				}

			} );
			return biggestSoFar;							
		}
		
		
		
		
		
		override public function dispose( ):void
		{
			
			super.dispose( );
			
			iCompareFunction = null;
		
		}
		
		
	}
	
}